Python emulator
Python backend
We report here the python backend, with all the available functions, coming from the package qtealeaves
- class qtealeaves.emulator.mps_simulator.MPS(num_sites, convergence_parameters, local_dim=2, initialize='vacuum', requires_singvals=False, tensor_backend=None, sectors=None, **kwargs)[source]
Matrix product states class
Parameters
- num_sites: int
Number of sites
- convergence_parameters:
TNConvergenceParameters Class for handling convergence parameters. In particular, in the MPS simulator we are interested in: - the maximum bond dimension \(\chi\); - the cut ratio \(\epsilon\) after which the singular
values are neglected, i.e. if \(\lamda_1\) is the bigger singular values then after an SVD we neglect all the singular values such that \(\frac{\lambda_i}{\lambda_1}\leq\epsilon\)
- local_dim: int or list of ints, optional
Local dimension of the degrees of freedom. Default to 2. If a list is given, then it must have length num_sites.
- initialize: str, optional
The method for the initialization. Default to “vacuum” Available: - “vacuum”, for the |000…0> state - “random”, for a random state at given bond dimension
- requires_singvalsboolean, optional
Allows to enforce SVD to have singular values on each link available which might be useful for measurements, e.g., bond entropy (the alternative is traversing the whole TN again to get the bond entropy on each link with an SVD).
- tensor_backendNone or instance of
TensorBackend Default for None is
QteaTensorwith np.complex128 on CPU.- sectorsdict, optional
Can restrict symmetry sector and/or bond dimension in initialization. If empty, no restriction. Default to None
- add_site(idx, state=None)[source]
Add a site in a product state in the link idx (idx=0 is before the first site, idx=N+1 is after the last). The state of the new index is |0> or the one provided.
Parameters
- idxint
index of the link where you want to add the site
- state: None or array-like
Vector state that you want to add
Details
To insert a new site in the MPS we first insert an identity on a link, then add a dimension-1 link to the identity and lastly contract the new link with the initial state, usually a |0>
- apply_mpo(mpo)[source]
Apply an MPO to the MPS on the sites sites. The MPO should have the following convention for the links: 0 is left link. 1 is physical link pointing downwards. 2 is phisical link pointing upwards. 3 is right link.
The sites are encoded inside the DenseMPO class.
Parameters
- mpoDenseMPO
MPO to be applied
Returns
- np.ndarray
Singular values cutted when the gate link is contracted
- apply_nonlocal_two_site_operator(op, control, target, swap=False)[source]
Apply a non-local two-site operator, by taking first the SVD of the operator, contracting the almost-single-site operator to the respective sites and then propagating the operator to the correct site
Warning
The operations in this method are NOT ALWAYS well defined. If the left-operator tensor is not unitary, then we are applying a non-unitary operation to the state, and thus we will see a vanishing norm. Notice that, if the error can happen a warning message will be issued
Parameters
- opnp.ndarray
Operator to be applied
- controlint
control qubit index
- targetint
target qubit index
- swapbool, optional
If True, transpose the tensor legs such that the control and target are swapped. Default to False
Returns
- np.ndarray
Singular values cutted when the gate link is contracted
- apply_one_site_operator(op, pos)[source]
Applies a one operator op to the site pos of the MPS.
Parameters
- op: QteaTensor of shape (local_dim, local_dim)
Matrix representation of the quantum gate
- pos: int
Position of the qubit where to apply op.
- apply_projective_operator(site, selected_output=None, remove=False)[source]
Apply a projective operator to the site site, and give the measurement as output. You can also decide to select a given output for the measurement, if the probability is non-zero. Finally, you have the possibility of removing the site after the measurement.
Warning
Applying projective measurements/removing sites is ALWAYS dangerous. The information of the projective measurement should be in principle carried over the entire mps, by iteratively applying SVDs across all sites. However, this procedure is highly suboptimal, since it is not always necessary and will be processed by the following two-sites operators. Thus, the procedure IS NOT applied here. Take care that entanglement measures through
TNObsBondEntropymay give incorrect results right after a projective operator application. Furthermore, if working with parallel approaches, projective operators should be treated with even more caution, since they CANNOT be applied in parallel.Parameters
- site: int
Index of the site you want to measure
- selected_output: int, optional
If provided, the selected state is measured. Throw an error if the probability of the state is 0
- remove: bool, optional
If True, the measured index is traced away after the measurement. Default to False.
Returns
- meas_state: int
Measured state
- state_probfloat
Probability of measuring the output state
- apply_two_site_operator(op, pos, swap=False, svd=True, parallel=False)[source]
Applies a two-site operator op to the site pos, pos+1 of the MPS.
Parameters
- op: QteaTensor (local_dim, local_dim, local_dim, local_dim)
Matrix representation of the quantum gate
- pos: int or list of ints
Position of the qubit where to apply op. If a list is passed, the two sites should be adjacent. The first index is assumed to be the control, and the second the target. The swap argument is overwritten if a list is passed.
- swap: bool
If True swaps the operator. This means that instead of the first contraction in the following we get the second. It is written is a list of pos is passed.
- svd: bool
If True, apply the usual contraction plus an SVD, otherwise use the QR approach explained in https://arxiv.org/pdf/2212.09782.pdf.
- parallel: bool
If True, perform an approximation of the two-qubit gates faking the isometry center
Returns
- singular_values_cutted: ndarray
Array of singular values cutted, normalized to the biggest singular value
Examples
swap=False swap=True -P-M- -P-M- 2| |2 2| |2 3| |4 4| |3 GGG GGG 1| |2 2| |1
- build_effective_operators(measurement_mode=False)[source]
Build the complete effective operator on each of the links. It assumes self.eff_op is set.
Parameters
- measurement_modebool, optional
If True, enable measurement mode of effective operators
- contract(other, boundaries=None)[source]
Contract the MPS with another MPS other <other|self>. By default it is a full contraction, but also a partial contraction is possible
Parameters
- otherMPS
other MPS to contract with
- boundariestuple of ints, optional
Contract to MPSs from boundaries[0] to boundaries[1]. In this case the output will be a tensor. Default to None, which is full contraction
Returns
- contractioncomplex
Result of the contraction
- property current_max_bond_dim
Maximum bond dimension of the mps
- property default_iso_pos
Returns default isometry center position, e.g., for initialization of effective operators.
- default_sweep_order(skip_exact_rgtensors=False)[source]
Default sweep order to be used in the ground state search/time evolution. Default for MPS is left-to-right.
Arguments
- skip_exact_rgtensorsbool, optional
Allows to exclude tensors from the sweep which are at full bond dimension and represent just a unitary transformation. Usually set via the convergence parameters and then passed here. Default to False.
Returns
- List[int]
The generator that you can sweep through
- deprecated_get_eff_op_on_pos(pos)[source]
Obtain the list of effective operators adjacent to the position pos and the index where they should be contracted
Parameters
- poslist
list of [layer, tensor in layer]
Returns
- list of IndexedOperators
List of effective operators
- list of ints
Indexes where the operators should be contracted
- dot(other)[source]
Calculate the dot-product or overlap between two MPSs, i.e., <self | other>.
Parameters
- other
MPS Measure the overlap with this other MPS.
Returns ——-a
Scalar representing the overlap.
- other
- property first_non_orthogonal_left
First non orthogonal tensor starting from the left
- property first_non_orthogonal_right
First non orthogonal tensor starting from the right
- classmethod from_statevector(statevector, local_dim=2, conv_params=None, tensor_backend=None)[source]
Initialize the MPS tensors by decomposing a statevector into MPS form. All the degrees of freedom must have the same local dimension
Parameters
- statevectorndarray of shape( local_dim^num_sites, )
Statevector describing the interested state for initializing the MPS
- local_dimint, optional
Local dimension of the degrees of freedom. Default to 2.
- conv_params
TNConvergenceParameters, optional Convergence parameters for the new MPS. If None, the maximum bond bond dimension possible is assumed, and a cut_ratio=1e-9. Default to None.
- tensor_backendNone or instance of
TensorBackend Default for None is
QteaTensorwith np.complex128 on CPU.
Returns
- obj
MPS MPS simulator class
Examples
>>> -U1 - U2 - U3 - ... - UN- >>> | | | | # For d=2, N=7 and chi=5, the tensor network is as follows: >>> -U1 -2- U2 -4- U3 -5- U4 -5- U5 -4- U6 -2- U7- >>> | | | | | | | # where -x- denotes the bounds' dimension (all the "bottom-facing" indices # are of dimension d=2). Thus, the shapes # of the returned tensors are as follows: >>> U1 U2 U3 U4 U5 U6 U7 >>> [(1, 2, 2), (2, 2, 4), (4, 2, 5), (5, 2, 5), (5, 2, 4), (4, 2, 2), (2, 2, 1)]
- classmethod from_tensor_list(tensor_list, conv_params=None, tensor_backend=None)[source]
Initialize the MPS tensors using a list of correctly shaped tensors
Parameters
- tensor_listlist of ndarrays or cupy arrays
List of tensor for initializing the MPS
- conv_params
TNConvergenceParameters, optional Convergence parameters for the new MPS. If None, the maximum bond bond dimension possible is assumed, and a cut_ratio=1e-9. Default to None.
- tensor_backendNone or instance of
TensorBackend Default for None is
QteaTensorwith np.complex128 on CPU.
Returns
- obj
MPS The MPS class
- get_bipartition_link(pos_src, pos_dst)[source]
Returns two sets of sites forming the bipartition of the system for a loopless tensor network. The link is specified via two positions in the tensor network.
Arguments
- pos_srctuple of two ints
Specifies the first tensor and source of the link.
- pos_dsttuple of two ints
Specifies the second tensor and destination of the link.
Returns
- sites_srclist of ints
Hilbert space indices when looking from the link towards source tensor and following the links therein.
- sites_dstlist of ints
Hilbert space indices when looking from the link towards destination tensor and following the links therein.
- get_pos_links(pos)[source]
List of tensor position where links are leading to.
Parameters
- posint
Index of the tensor in the MPS
Returns
- Tuple[int]
Index of the tensor connected through links to pos. None if they are open links.
- get_pos_partner_link_expansion(pos)[source]
Get the position of the partner tensor to use in the link expansion subroutine. It is the tensor towards the center, that is supposed to be more entangled w.r.t. the tensor towards the edge
Parameters
- posint
Position w.r.t. which you want to compute the partner
Returns
- int
Position of the partner
- int
Link of pos pointing towards the partner
- int
Link of the partner pointing towards pos
- get_rho_i(idx)[source]
Get the reduced density matrix of the site at index idx
Parameters
- idxint
Index of the site
Returns
_AbstractQteaTensorReduced density matrix of the site
- get_tensor_of_site(idx)[source]
Generic function to retrieve the tensor for a specific site. Compatible across different tensor network geometries. This function does not shift the gauge center before returning the tensor.
Parameters
- idxint
Return tensor containing the link of the local Hilbert space of the idx-th site.
- property iso_center
Output the gauge center if it is well defined, otherwise None
- iso_towards(new_iso, keep_singvals=False, trunc=False, conv_params=None, move_to_memory_device=True, normalize=False)[source]
Apply the gauge transformation to shift the isometry center to a specific site new_iso. The method might be different for other TN structure, but for the MPS it is the same.
Parameters
- new_isoint
Position in the TN of the tensor which should be isometrized.
- keep_singvalsbool, optional
If True, keep the singular values even if shifting the iso with a QR decomposition. Default to False.
- truncBoolean, optional
If True, the shifting is done via truncated SVD. If False, the shifting is done via QR. Default to False.
- conv_params
TNConvergenceParameters, optional Convergence parameters to use for the SVD. If None, convergence parameters are taken from the TTN. Default to None.
- move_to_memory_devicebool, optional
If True, when a mixed device is used, move the tensors that are not the isometry center back to the memory device. Default to True.
- normalizebool, optional
Flag if intermediate steps should normalize. Default to False
Details
The tensors used in the computation will always be moved on the computational device. For example, the isometry movement keeps the isometry center end the effective operators around the center (if present) always on the computational device. If move_to_memory_device is False, then all the tensors (effective operators) on the path from the old iso to the new iso will be kept in the computational device. This is very useful when you iterate some protocol between two tensors, or in general when two tensors are involved.
- kron(other, inplace=False)[source]
Concatenate two MPS, taking the kronecker/outer product of the two states. The bond dimension assumed is the maximum between the two bond dimensions.
Parameters
- other
MPS MPS to concatenate
- inplacebool, optional
If True apply the kronecker product in place. Instead, if inplace=False give as output the product. Default to False.
Returns
MPSConcatenation of the first MPS with the second in order
- other
- left_canonize(idx, trunc=False, keep_singvals=False, conv_params=None, move_to_memory_device=True, normalize=False)[source]
Apply a gauge transformation to all bonds between 0 and idx, so that all sites between the first (òeftmpst one) and idx are set to (semi)-unitary tensors.
Parameters
- idx: int
index of the tensor up to which the canonization occurs
- trunc: bool, optional
If True, use the SVD instead of the QR for the canonization. It might be useful to reduce the bond dimension. Default to False.
- keep_singvalsbool, optional
If True, keep the singular values even if shifting the iso with a QR decomposition. Default to False.
- conv_params
TNConvergenceParameters, optional Convergence parameters to use for the SVD in the procedure. If None, convergence parameters are taken from the TTN. Default to None.
- move_to_memory_devicebool, optional
If True, when a mixed device is used, move the tensors that are not the isometry center back to the memory device. Default to True.
- normalizebool, optional
Flag if singular values should be normalized. Default to False
- meas_bond_entropy()[source]
Measure the entanglement entropy along all the sites of the MPS using the Von Neumann entropy \(S_V\) defined as:
\[S_V = - \sum_i^{\chi} s^2 \ln( s^2)\]with \(s\) the singular values
Return
- measuresdict
Keys are the range of the bipartition from 0 to which the entanglement (value) is relative
- meas_even_probabilities(threshold, qiskit_convention=False)[source]
Compute the probabilities of measuring a given state if it is greater than a threshold. The function goes down “evenly” on the probability tree. This means that there is the possibility that no state is returned, if their probability is lower then threshold. Furthermore, notice that the maximum number of states returned is :math:`(
rac{1}{threshold})`.
For a different way of computing the probability tree see the function
meas_greedy_probabilities()ormeas_unbiased_probabilities().- thresholdfloat
Discard all the probabilities lower then the threshold
- qiskit_conventionbool, optional
If the sites during the measure are represented such that |201> has site 0 with value one (True, mimicks bits ordering) or with value 2 (False usually used in theoretical computations). Default to False.
- probabilitiesdict
Dictionary where the keys are the states while the values their probabilities. The keys are separated by a comma if local_dim > 9.
- meas_greedy_probabilities(max_prob, max_iter=None, qiskit_convention=False)[source]
Compute the probabilities of measuring a given state until the total probability measured is greater than the threshold max_prob. The function goes down “greedily” on the probability tree. This means that there is the possibility that a path that was most promising at the tree root will become very computationally demanding and not so informative once reached the leaves. Furthermore, notice that there is no maximum number of states returned, and so the function might be exponentially slow.
For a different way of computing the probability tree see the function
meas_even_probabilities()ormeas_unbiased_probabilities()Parameters
- max_probfloat
Compute states until you reach this probability
- qiskit_conventionbool, optional
If the sites during the measure are represented such that |201> has site 0 with value one (True, mimicks bits ordering) or with value 2 (False usually used in theoretical computations). Default to False.
Return
- probabilitiesdict
Dictionary where the keys are the states while the values their probabilities. The keys are separated by a comma if local_dim > 9.
- meas_tensor_product(ops, idxs)[source]
Measure the tensor products of n operators ops acting on the indexes idxs. The operators should be MPOs, i.e. rank-4 tensors of shape (left, up, down, right). To retrieve the tensor product operators, left=right=1.
Parameters
- opslist of ndarrays
List of numpy arrays which are one-site operators
- idxslist of int
Indexes where the operators are applied
Returns
- measurefloat
Result of the measurement
- meas_weighted_sum(op_strings, idxs_strings, coefs)[source]
Measure the weighted sum of tensor product operators. See
meas_tensor_product()Parameters
- op_stringslist of lists of ndarray
list of tensor product operators
- idxs_stringslist of list of int
list of indexes of tensor product operators
- coefslist of complex
list of the coefficients of the sum
Return
- measurecomplex
Result of the measurement
- ml_get_gradient_tensor(idx, data_sample, true_label)[source]
Get the gradient w.r.t. the tensors at position idx, idx+1 of the MPS following the procedure explained in https://arxiv.org/pdf/1605.05775.pdf for the data_sample given
Parameters
- idxint
Index of the tensor to optimize
- data_samplepy:class:MPS
Data sample in MPS class
- true_labelint
True label of the datasample
Returns
- xp.ndarray
Gradient tensor
- ml_optimize_mps(data_samples, true_labels, batch_size, learning_rate, num_sweeps, n_jobs=1)[source]
Optimize the MPS using the algorithm of Stoudenmire
Parameters
- data_samplesList[py:class:MPS]
Feature dataset
- true_labelsList[int]
Labels of the dataset
- batch_sizeint
Number of samples for a single sweep(epoch)
- learning_ratefloat or callable
Learning rate for the tensor update. If callable, it can depend on the sweep.
- num_sweepsint
Number of optimization sweeps (epochs)
- n_jobsint, optional
Number of parallel jobs for the optimization, by default 1
Returns
- xp.ndarray
Singular values cut in the optimization
- xp.ndarray
Value of the loss function at each sweep(epoch)
- ml_optmize_tensor(idx, data_samples, true_labels, learning_rate, n_jobs=1, direction=1)[source]
Optimize a single tensor using a batch of data damples
Parameters
- idxint
Index of the tensor to optimize
- data_samplesList[py:class:MPS]
List of data samples
- true_labelsxp.ndarray
List of labels (0 or 1)
- learning_ratefloat
Learining rate for the tensor update
- n_jobsint, optional
Number of parallel jobs for the optimization, by default 1
Returns
- xp.ndarray
Singular values cut in the optimization
- float
Value of the loss function
- ml_predict(data_samples, n_jobs=1)[source]
Predict the labels of the data samples passed
Parameters
- data_samplesList[py:class:MPS]
Feature dataset
- true_labelsList[int]
Labels of the dataset
- n_jobsint, optional
Number of parallel jobs for the optimization, by default 1
Returns
- List
Predicted labels
- modify_local_dim(value, idxs=None)[source]
Modify the local dimension of sites idxs to the value value. By default modify the local dimension of all the sites. If value is a vector then it must have the same length of idxs. Notice that there may be loss of information, it is up to the user to be sure no error is done in this procedure.
Parameters
- valueint or array-like
New value of the local dimension. If an int, it is assumed it will be the same for all sites idxs, otherwise its length must be the same of idxs.
- idxsint or array-like, optional
Indexes of the sites to modify. If None, all the sites are modified. Default to None.
- classmethod mpi_bcast(state, comm, tensor_backend, root=0)[source]
Broadcast a whole tensor network.
Arguments
- state
MPS(for MPI-rank root, otherwise None is acceptable) State to be broadcasted via MPI.
- commMPI communicator
Send state to this group of MPI processes.
- tensor_backend
TensorBackend Needed to identity data types and tensor classes on receiving MPI threads (plus checks on sending MPI thread).
- rootint, optional
MPI-rank of sending thread with the state. Default to 0.
- state
- static mpi_sample_n_unique_states(state, num_unique, comm, tensor_backend, cache_size=None, cache_clearing_strategy=None, filter_func=None, mpi_final_op=None, root=0, **kwargs)[source]
Try sampling a target number of unique states from TN ansatz.
- mps_multiply_mps(other)[source]
Elementwise multiplication of the MPS with another MPS, resulting multiplying the coefficients of the statevector representation. If self represents the state a|000>+b|111> and other represent c|000>+d|111> then self.mps_multiply_mps(other)=ac|000>+bd|111>. It is very computationally demanding and the new bond dimension is the product of the two original bond dimensions.
Parameters
- otherMPS
MPS to multiply
Returns
- MPS
Summation of the first MPS with the second
- property physical_idxs
Physical indices property
- classmethod read(filename, tensor_backend, cmplx=True, order='F')[source]
Read an MPS written by FORTRAN in a formatted way on file. Reads in column-major order but the output is in row-major. This is the only method that overrides the number of sites, since you may not know before reading.
Parameters
- filename: str
PATH to the file
- tensor_backend
TensorBackend Setup which tensor class to create.
- cmplx: bool, optional
If True the MPS is complex, real otherwise. Default to True
- order: str, optional
If ‘F’ the tensor is transformed from column-major to row-major, if ‘C’ it is left as read.
Returns
- obj: py:class:MPS
MPS class read from file
- reset(idxs=None)[source]
Reset the states of the sites idxs to the |0> state
Parameters
- idxsint or list of ints, optional
indexes of the sites to reinitialize to 0. If default value is left all the sites are restarted.
- right_canonize(idx, trunc=False, keep_singvals=False, conv_params=None, move_to_memory_device=True, normalize=False)[source]
Apply a gauge transformation to all bonds between :py:method:`MPS.num_sites` and idx, so that all sites between the last (rightmost one) and idx are set to (semi)-unitary tensors.
Parameters
- idx: int
index of the tensor up to which the canonization occurs
- trunc: bool, optional
If True, use the SVD instead of the QR for the canonization. It might be useful to reduce the bond dimension. Default to False.
- keep_singvalsbool, optional
If True, keep the singular values even if shifting the iso with a QR decomposition. Default to False.
- conv_params
TNConvergenceParameters, optional Convergence parameters to use for the SVD in the procedure. If None, convergence parameters are taken from the TTN. Default to None.
- move_to_memory_devicebool, optional
If True, when a mixed device is used, move the tensors that are not the isometry center back to the memory device. Default to True.
- normalizebool, optional
Flag if intermediate steps should normalize. Default to False
- scale(factor)[source]
Scale the MPS state by a scalar constant using the gauge center.
Parameters
- factorscalar
Factor is multiplied to the MPS at the gauge center.
- set_singvals_on_link(pos_a, pos_b, s_vals)[source]
Update or set singvals on link via two positions.
- property singvals
List of singular values in the bonds
- site_canonize(idx, keep_singvals=False, normalize=False)[source]
Apply the gauge transformation to shift the isometry center to a specific site idx.
Parameters
- idx: int
index of the tensor up to which the canonization occurs from the left and right side.
- keep_singvalsbool, optional
If True, keep the singular values even if shifting the iso with a QR decomposition. Default to False.
- normalizebool, optional
Flag if intermediate steps should normalize. Default to False
- swap_qubits(sites, conv_params=None, trunc=True)[source]
This function applies a swap gate to sites in an MPS, i.e. swaps these two qubits
Parameters
- sitesTuple[int]
The qubits on site sites[0] and sites[1] are swapped
- conv_params
TNConvergenceParameters, optional Convergence parameters to use for the SVD in the procedure. If None, convergence parameters are taken from the TTN. Default to None.
Return
- np.ndarray
Singualr values cut in the process of shifting the isometry center. None if moved through the QR.
- property tensors
List of MPS tensors
- to_dense(true_copy=False)[source]
Return MPS without symmetric tensors.
Parameters
- true_copybool, optional
The function can be forced to return an actual copy with true_copy=True, while otherwise self can be returned if the MPS is already without symmetries. Default to False
Returns
- dense_mps
MPS MPS representation without symmetric tensors.
- to_statevector(qiskit_order=False, max_qubit_equivalent=20)[source]
Given a list of N tensors MPS [U1, U2, …, UN] , representing a Matrix Product State, perform the contraction in the Examples, leading to a single tensor of order N, representing a dense state.
The index ordering convention is from left-to-right. For instance, the “left” index of U2 is the first, the “bottom” one is the second, and the “right” one is the third.
Parameters
- qiskit_order: bool, optional
weather to use qiskit ordering or the theoretical one. For example the state |011> has 0 in the first position for the theoretical ordering, while for qiskit ordering it is on the last position.
- max_qubit_equivalent: int, optional
Maximum number of qubit sites the MPS can have and still be transformed into a statevector. If the number of sites is greater, it will throw an exception. Default to 20.
Returns
- psindarray of shape (d ^ N, )
N-order tensor representing the dense state.
Examples
>>> U1 - U2 - ... - UN >>> | | |
- to_tensor_list()[source]
Return the tensor list representation of the MPS. Required for compatibility with TTN emulator
Return
- list
List of tensors of the MPS
- to_ttn()[source]
Return a tree tensor network (TTN) representation as binary tree.
Details
The TTN is returned as a listed list where the tree layer with the local Hilbert space is the first list entry and the uppermost layer in the TTN is the last list entry. The first list will have num_sites / 2 entries. The uppermost list has two entries.
The order of the legs is always left-child, right-child, parent with the exception of the left top tensor. The left top tensor has an additional link, i.e., the symmetry selector; the order is left-child, right-child, parent, symmetry-selector.